﻿using JiveMessenger.Converters;
using JiveMessenger.Models;
using JiveMessenger.Utilities;
using JiveMessenger.ViewModels;
using JmShared;
using JmShared.Models;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;

namespace JiveMessenger.CustomControls
{
    /// <summary>
    /// Interaction logic for ManageGroupControl.xaml
    /// </summary>
    public partial class ManageGroupControl : UserControl,IDisposable
    {
        private BackgroundWorker _changeGroupPrivilegeWorker;
        public ManageGroupControl()
        {
            InitializeComponent();
            _changeGroupPrivilegeWorker = new BackgroundWorker();
            _changeGroupPrivilegeWorker.DoWork += _changeGroupPrivilegeWorker_DoWork;
            _changeGroupPrivilegeWorker.RunWorkerCompleted += _changeGroupPrivilegeWorker_RunWorkerCompleted;
        }

        private void _changeGroupPrivilegeWorker_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
        {
            Tuple<DatabaseQueryResponse, ComboBox, GroupPrivilege> args = (Tuple<DatabaseQueryResponse,ComboBox, GroupPrivilege>)e.Result;
            ComboBox cb = (ComboBox)args.Item2;
            if (!args.Item1.Success)
            {

                cb.Tag = true;
                cb.SelectedItem = args.Item3;
                IGroupMember member = (IGroupMember)cb.DataContext;
                member.Privilege = args.Item3;
                cb.UpdateLayout();
                MessageBox.Show(args.Item1.StatusText);
            }
            cb.IsEnabled = true;
        }

        private void _changeGroupPrivilegeWorker_DoWork(object sender, DoWorkEventArgs e)
        {
            Tuple<GroupPrivilege, ComboBox, MemberGroupPrivilege> args = (Tuple<GroupPrivilege, ComboBox, MemberGroupPrivilege>)e.Argument;

            var response = VmHelper.Locator.CurrentClient.Connection.SetGroupPrivilegeForUser(args.Item3);

            e.Result = new Tuple<DatabaseQueryResponse,ComboBox, GroupPrivilege>(response,args.Item2, args.Item1);
        }


        private void CbGroupPrivilege_SelectionChanged(object sender, SelectionChangedEventArgs e)
        {
            ComboBox cb = (ComboBox)sender;
            IGroupMember member = (IGroupMember)cb.DataContext;
            if (e.RemovedItems.Count == 0 || e.AddedItems.Count == 0)//this is true when we initially load the combobox items, so we just return;
                return;
            if (cb.Tag != null && (bool)cb.Tag == true)
            {
                cb.Tag = false;
                return;
            }
            var privilege = e.AddedItems[0];
            MessageBoxResult result = MessageBox.Show(string.Format("Change privilege for {0} from {1} to {2}?", member.Username, StaticMethods.GetEnumDescription(member.Privilege), privilege), "Change Privilege", MessageBoxButton.OKCancel);
            if (result == MessageBoxResult.OK)
            {
                cb.IsEnabled = false;
                MemberGroupPrivilege priv = new MemberGroupPrivilege(member.Username, Convert.ToInt32(((ViewModelManageGroup)this.DataContext).ChatGroup.ID), (GroupPrivilege)privilege);
                _changeGroupPrivilegeWorker.RunWorkerAsync(new Tuple<GroupPrivilege, ComboBox, MemberGroupPrivilege>(member.Privilege, cb, priv));

                        member.Privilege = (GroupPrivilege)privilege;
            }
            else
            {
                cb.Tag = true;
                cb.SelectedItem = member.Privilege;
            }
        }

        private bool FilterOwnerPrivileges(object p)
        {
            if (p is GroupPrivilege)
            {
                var privilege = (GroupPrivilege)p;
                var vm = (ViewModelManageGroup)this.DataContext;
                GroupPrivilege currentUserPrivilege = vm.GroupMembers.FirstOrDefault(x => x.Username == VmHelper.Locator.CurrentClient.CurrentUserInfo.UserName).Privilege;
                switch (currentUserPrivilege)
                {
                    case GroupPrivilege.Owner:
                        return privilege == GroupPrivilege.Owner;
                    case GroupPrivilege.Moderator:
                        return privilege == GroupPrivilege.Owner;
                    default:
                        return privilege == GroupPrivilege.Owner;
                }
            }
            else
                return false;
        }
        private bool FilterMemberPrivileges(object p)
        {
            if (p is GroupPrivilege)
            {
                var privilege = (GroupPrivilege)p;
                var vm = (ViewModelManageGroup)this.DataContext;
                GroupPrivilege currentUserPrivilege = vm.GroupMembers.FirstOrDefault(x => x.Username == VmHelper.Locator.CurrentClient.CurrentUserInfo.UserName).Privilege;
                switch (currentUserPrivilege)
                {
                    case GroupPrivilege.Owner:
                        return privilege == GroupPrivilege.Member || privilege == GroupPrivilege.Moderator;
                    case GroupPrivilege.Moderator:
                        return privilege == GroupPrivilege.Member;
                    default:
                        return privilege == GroupPrivilege.Member;
                }
            }
            else
                return false;
        }
        private bool FilterModeratorPrivileges(object p)
        {
            if (p is GroupPrivilege)
            {
                var privilege = (GroupPrivilege)p;
                var vm = (ViewModelManageGroup)this.DataContext;
                GroupPrivilege currentUserPrivilege = vm.GroupMembers.FirstOrDefault(x => x.Username == VmHelper.Locator.CurrentClient.CurrentUserInfo.UserName).Privilege;
                switch (currentUserPrivilege)
                {
                    case GroupPrivilege.Owner:
                        return privilege == GroupPrivilege.Member || privilege == GroupPrivilege.Moderator;
                    case GroupPrivilege.Moderator:
                        return privilege == GroupPrivilege.Member || privilege == GroupPrivilege.Moderator;
                    default:
                        return privilege == GroupPrivilege.Member || privilege == GroupPrivilege.Moderator;
                }

            }
            else
                return false;
        }
        private void CbGroupPrivilege_DropDownOpened(object sender, EventArgs e)
        {
            ComboBox cb = (ComboBox)sender;
            IGroupMember member = (IGroupMember)cb.DataContext;
            Predicate<object> prd = null;
            if (member.Privilege == GroupPrivilege.Owner)
                prd = new Predicate<object>(FilterOwnerPrivileges);
            else if (member.Privilege == GroupPrivilege.Moderator)
                prd = new Predicate<object>(FilterModeratorPrivileges);
            else if (member.Privilege == GroupPrivilege.Member)
                prd = new Predicate<object>(FilterMemberPrivileges);
            cb.Items.Filter = null;
            cb.Items.Filter = prd;

            //var vm = (ViewModelManageGroup)this.DataContext;
            //GroupPrivilege currentUserPrivilege = vm.GroupMembers.FirstOrDefault(x => x.Username == VmHelper.Locator.CurrentClient.CurrentUserInfo.UserName).Privilege;
        }


        private void CbGroupPrivilege_Loaded(object sender, RoutedEventArgs args)
        {

            ComboBox cb = (ComboBox)sender;
            IGroupMember member = (IGroupMember)cb.DataContext;
            CollectionViewSource src = new CollectionViewSource();
            src.Source = Enum.GetValues(member.Privilege.GetType())
            .Cast<object>().Select(x => x);

            cb.ItemsSource = src.View;
        }

        private void UserControl_Loaded(object sender, RoutedEventArgs e)
        {
            if (DesignerProperties.GetIsInDesignMode(this))
                return;
            var conv = this.Resources["ComboboxDisableConverter"] as ComboboxDisableConverter;
            if (conv != null)
            {
                conv.CurrentChatGroup = ((ViewModelManageGroup)this.DataContext).ChatGroup as JiveChatGroupModel;
                conv.CurrentUser = VmHelper.Locator.ViewModelContactList.CurrentUser;
            }
        }

        public void Dispose()
        {

            _changeGroupPrivilegeWorker.DoWork -= _changeGroupPrivilegeWorker_DoWork;
            _changeGroupPrivilegeWorker.RunWorkerCompleted -= _changeGroupPrivilegeWorker_RunWorkerCompleted;
            _changeGroupPrivilegeWorker = null;
        }
    }
}
